<!DOCTYPE html>
<html lang="en">

<head>
  <title>Canvas interpolation example - Cannon.js</title>
  <meta charset="utf-8">
  <script src="../node_modules/feng3d/dist/index.js"></script>
  <script src="../dist/index.js"></script>
</head>

<body>

  <!-- The canvas, where we draw stuff -->
  <canvas width="500" height="500" id="myCanvas"></canvas>

  <script>
    var w, h, canvas, ctx, world, sphereBody;

    init();
    animate();

    function init()
    {

      // Init canvas
      canvas = document.getElementById("myCanvas");
      w = canvas.width;
      h = canvas.height;
      ctx = canvas.getContext("2d");
      ctx.lineWidth = 0.05;

      // Init world
      world = new CANNON.World({ gravity: new CANNON.Vector3() });

      // Add a circle
      sphereShape = new CANNON.Sphere(1);
      var velo = [0, 0],
        pos = [-3, 0];
      sphereBody = new CANNON.Body({ mass: 1, position: new CANNON.Vector3(-3, 0, 0) });
      sphereBody.damping = 0;
      sphereBody.addShape(sphereShape);
      world.addBody(sphereBody);
    }

    function drawCircles(ctx, sphereBody)
    {
      ctx.beginPath();
      var radius = sphereShape.radius;

      // Draw the circle at the interpolated position
      ctx.arc(sphereBody.interpolatedPosition.x,
        sphereBody.interpolatedPosition.y,
        radius, 0, 2 * Math.PI);
      ctx.stroke();
      ctx.beginPath();

      // Draw the circle at the fixed step position
      ctx.arc(sphereBody.position.x,
        sphereBody.position.y,
        radius, 0, 2 * Math.PI);
      ctx.stroke();
    }

    function render(ctx, sphereBody)
    {
      ctx.clearRect(0, 0, w, h);
      ctx.save();
      ctx.translate(w / 2, h / 2);
      ctx.scale(50, -50);
      drawCircles(ctx, sphereBody);
      ctx.restore();
    }

    var lastCallTime = time();

    // Animation loop
    function animate(t)
    {
      t = t || 0;
      requestAnimationFrame(animate);

      sphereBody.velocity.x = 2 * Math.cos(1 * t / 1000 + 3 / 2 * Math.PI);
      sphereBody.velocity.y = 2 * Math.sin(1 * t / 1000 + 3 / 2 * Math.PI);

      // Compute time since last time we called the .step() method
      var timeSinceLastCall = time() - lastCallTime;
      lastCallTime = time();

      // Fixed time step to use for physics. We use a huge timestep of 0.5 to see what's going on.
      // NOTE: For most games, fixedTimeStep=1/60 is a good choice.
      var fixedTimeStep = 0.5; // seconds

      // Max number of fixed physics timesteps to do in one .step(). We choose a large number to see what is going on.
      // NOTE: for most games, maxSubSteps=3 is probably a good choice.
      var maxSubSteps = 10;

      // Now step the world.
      // This will do integration at a fixed time step, but compute interpolated positions
      // which are stored in body.interpolatedPosition.
      world.step(fixedTimeStep, timeSinceLastCall, maxSubSteps);

      // Render both interpolated and fixed-step positions
      render(ctx, sphereBody);
    }

    // Get current time, in seconds.
    function time()
    {
      return new Date().getTime() / 1000;
    }
  </script>

</body>

</html>